import sys
import os
import subprocess
import platform
import tempfile
import base64
from PyQt5.QtWidgets import (QApplication, QMainWindow, QPushButton, QFileDialog, 
                            QVBoxLayout, QHBoxLayout, QWidget, QLabel, QLineEdit,
                            QProgressBar, QMessageBox, QFrame, QStyleFactory,
                            QCheckBox, QComboBox, QTextEdit, QTabWidget, QDialog)
from PyQt5.QtCore import QThread, pyqtSignal, Qt, QTimer
from PyQt5.QtGui import QIcon, QFont, QPalette, QColor, QPixmap
from icon_data import get_3d_data, get_mark_data
import pywinstyles
# 导入VideoProcessingThread类
from video_processing import VideoProcessingThread, HW_ACCEL_NONE, HW_ACCEL_NVIDIA, HW_ACCEL_AMD, HW_ACCEL_INTEL

class MainWindow(QMainWindow):
    def __init__(self):
        super().__init__()
        self.setWindowTitle("裸眼3D视频转换工具")
        self.setGeometry(100, 100, 650, 500)
        
        self.ffmpeg_path = ""
        self.input_files = []
        self.processing_thread = None
        
        self.set_style()
        self.init_ui()
        
        # 设置图标并在显示后应用样式
        self.setWindowIcon(self.create_icon_from_data())
        if platform.system() == "Windows":
            self.apply_acrylic_effect()
        
        # 窗口居中显示
        self.center_window()
    
    def center_window(self):
        """将窗口居中显示在屏幕上"""
        frame_geometry = self.frameGeometry()
        screen_center = QApplication.desktop().availableGeometry().center()
        frame_geometry.moveCenter(screen_center)
        self.move(frame_geometry.topLeft())
    
    def create_icon_from_data(self):
        try:
            icon_data = get_3d_data()
            svg_data = base64.b64decode(icon_data)
            pixmap = QPixmap()
            pixmap.loadFromData(svg_data)
            return QIcon(pixmap)
        except Exception as e:
            print(f"创建图标失败: {e}")
            return QIcon()

    def apply_acrylic_effect(self):
        """应用毛玻璃特效，仅限 Windows"""
        try:
            pywinstyles.apply_style(self, "acrylic")
            pywinstyles.change_border_color(self, color="#CCFFFF")
        except Exception as e:
            print(f"应用毛玻璃特效失败: {e}")
    
    def set_style(self):
        QApplication.setStyle(QStyleFactory.create("Fusion"))
        
        palette = QPalette()
        palette.setColor(QPalette.Window, QColor(53, 53, 53))
        palette.setColor(QPalette.WindowText, Qt.white)
        palette.setColor(QPalette.Button, QColor(53, 53, 53))
        palette.setColor(QPalette.ButtonText, Qt.white)
        palette.setColor(QPalette.Highlight, QColor(42, 130, 218))
        palette.setColor(QPalette.Text, Qt.white)
        palette.setColor(QPalette.Base, QColor(25, 25, 25))
        
        QApplication.setPalette(palette)
        
        # 设置所有输入控件的样式
        self.input_style = """
            QLineEdit {
                border: 1px solid #aaaaaa;
                border-radius: 3px;
                padding: 2px;
                background-color: #333333;
            }
            QLineEdit:disabled {
                border: 1px solid #555555;
                background-color: #444444;
            }
        """
        
        # 添加QCheckBox样式
        self.checkbox_style = """
            QCheckBox {
                spacing: 5px;
            }
            QCheckBox::indicator {
                width: 15px;
                height: 15px;
                border: 1px solid #aaaaaa;
                border-radius: 3px;
                background-color: #333333;
            }
            QCheckBox::indicator:checked {
                background-color: #2a82da;
                border: 1px solid #aaaaaa;
                image: url(check.png);
            }
            QCheckBox::indicator:unchecked:hover {
                border: 1px solid #ffffff;
            }
        """
    
    def init_ui(self):
        main_widget = QWidget()
        main_layout = QVBoxLayout()
        main_layout.setSpacing(15)
        main_layout.setContentsMargins(20, 20, 20, 20)
        
        title_label = QLabel("裸眼3D视频转换工具")
        title_label.setAlignment(Qt.AlignCenter)
        title_font = QFont("Arial", 16, QFont.Bold)
        title_label.setFont(title_font)
        main_layout.addWidget(title_label)
        
        line = QFrame()
        line.setFrameShape(QFrame.HLine)
        line.setFrameShadow(QFrame.Sunken)
        main_layout.addWidget(line)
        
        # 直接添加各个布局到主布局，不使用选项卡
        ffmpeg_layout = QHBoxLayout()
        ffmpeg_label = QLabel("FFmpeg路径:")
        self.ffmpeg_path_edit = QLineEdit()
        self.ffmpeg_path_edit.setReadOnly(True)
        self.ffmpeg_path_edit.setStyleSheet(self.input_style)
        ffmpeg_button = QPushButton("选择FFmpeg")
        ffmpeg_button.clicked.connect(self.select_ffmpeg)
        
        ffmpeg_layout.addWidget(ffmpeg_label)
        ffmpeg_layout.addWidget(self.ffmpeg_path_edit)
        ffmpeg_layout.addWidget(ffmpeg_button)
        
        input_layout = QHBoxLayout()
        input_label = QLabel("输入:")
        self.input_path_edit = QLineEdit()
        self.input_path_edit.setReadOnly(True)
        self.input_path_edit.setStyleSheet(self.input_style)
        file_button = QPushButton("选择文件")
        file_button.clicked.connect(self.select_file)
        folder_button = QPushButton("选择文件夹")
        folder_button.clicked.connect(self.select_folder)
        
        input_layout.addWidget(input_label)
        input_layout.addWidget(self.input_path_edit)
        input_layout.addWidget(file_button)
        input_layout.addWidget(folder_button)
        
        offset_layout = QHBoxLayout()
        offset_label = QLabel("时间偏移(毫秒):")
        self.offset_edit = QLineEdit("30")
        self.offset_edit.setStyleSheet(self.input_style)
        offset_layout.addWidget(offset_label)
        offset_layout.addWidget(self.offset_edit)
        
        # 在黑线布局中应用样式
        black_line_layout = QHBoxLayout()
        black_line_label = QLabel("视频中间添加黑色细杠:")
        self.black_line_checkbox = QCheckBox()
        self.black_line_checkbox.setStyleSheet(self.checkbox_style)
        black_line_width_label = QLabel("细杠粗细:")
        self.black_line_width_edit = QLineEdit("1")
        self.black_line_width_edit.setFixedWidth(50)
        self.black_line_width_edit.setStyleSheet(self.input_style)
        self.black_line_checkbox.stateChanged.connect(self.toggle_black_line_width)
        self.black_line_width_edit.setEnabled(False)
        
        black_line_layout.addWidget(black_line_label)
        black_line_layout.addWidget(self.black_line_checkbox)
        black_line_layout.addWidget(black_line_width_label)
        black_line_layout.addWidget(self.black_line_width_edit)
        black_line_layout.addStretch()
        
        # 修改水印布局，添加尺寸调节选项
        watermark_layout = QHBoxLayout()
        watermark_label = QLabel("在视频底部添加标记图片:")
        self.watermark_checkbox = QCheckBox()
        self.watermark_checkbox.setStyleSheet(self.checkbox_style)
        
        # 添加水印尺寸调节
        watermark_size_label = QLabel("图片尺寸倍数:")
        self.watermark_size_edit = QLineEdit("1.0")
        self.watermark_size_edit.setFixedWidth(50)
        self.watermark_size_edit.setStyleSheet(self.input_style)
        preview_button = QPushButton("预览图片")
        preview_button.clicked.connect(self.preview_watermark)
        preview_button.setStyleSheet(self.input_style)
        watermark_layout.addWidget(watermark_label)
        watermark_layout.addWidget(self.watermark_checkbox)
        watermark_layout.addWidget(watermark_size_label)
        watermark_layout.addWidget(self.watermark_size_edit)
        watermark_layout.addWidget(preview_button)
        watermark_layout.addStretch()
        
        hint_layout = QHBoxLayout()
        hint_label = QLabel("提示: 短片适合30毫秒，电视剧适合20毫秒")
        hint_label.setStyleSheet("color: #aaaaaa; font-style: italic;")
        hint_layout.addWidget(hint_label)
        
        # 添加硬件加速选择
        hw_accel_layout = QHBoxLayout()
        hw_accel_label = QLabel("硬件加速:")
        self.hw_accel_combo = QComboBox()
        self.hw_accel_combo.addItem(HW_ACCEL_NONE)  # 默认添加CPU选项
        self.hw_accel_combo.setStyleSheet(self.input_style)
        scan_hw_button = QPushButton("扫描硬件")
        scan_hw_button.clicked.connect(self.update_hw_acceleration)
        gpu_info_button = QPushButton("GPU信息")
        gpu_info_button.clicked.connect(self.show_gpu_info)
        
        hw_accel_layout.addWidget(hw_accel_label)
        hw_accel_layout.addWidget(self.hw_accel_combo)
        hw_accel_layout.addWidget(scan_hw_button)
        hw_accel_layout.addWidget(gpu_info_button)
        hw_accel_layout.addStretch()
        
        button_layout = QHBoxLayout()
        self.process_button = QPushButton("开始处理")
        self.process_button.setMinimumHeight(40)
        self.process_button.setStyleSheet("background-color: #2a82da; font-weight: bold;")
        self.process_button.clicked.connect(self.start_processing)
        
        self.cancel_button = QPushButton("取消")
        self.cancel_button.setMinimumHeight(40)
        self.cancel_button.clicked.connect(self.cancel_processing)
        self.cancel_button.setEnabled(False)
        
        button_layout.addWidget(self.process_button)
        button_layout.addWidget(self.cancel_button)
        
        progress_layout = QVBoxLayout()
        self.current_file_label = QLabel("准备就绪")
        self.current_file_label.setAlignment(Qt.AlignCenter)
        self.progress_bar = QProgressBar()
        self.progress_bar.setTextVisible(True)
        self.progress_bar.setAlignment(Qt.AlignCenter)
        self.progress_bar.setStyleSheet(
            "QProgressBar {border: 1px solid grey; border-radius: 3px; text-align: center;}"
            "QProgressBar::chunk {background-color: #2a82da;}"
        )
        
        progress_layout.addWidget(self.current_file_label)
        progress_layout.addWidget(self.progress_bar)
        
        # 添加日志显示框
        log_layout = QVBoxLayout()
        log_label = QLabel("处理日志:")
        self.log_text = QTextEdit()
        self.log_text.setReadOnly(True)
        self.log_text.setStyleSheet("background-color: #222222; color: #cccccc; font-family: Consolas, monospace;")
        self.log_text.setMinimumHeight(150)
        log_layout.addWidget(log_label)
        log_layout.addWidget(self.log_text)
        
        # 将所有布局直接添加到主布局
        main_layout.addLayout(ffmpeg_layout)
        main_layout.addLayout(input_layout)
        main_layout.addLayout(offset_layout)
        main_layout.addLayout(black_line_layout)
        main_layout.addLayout(watermark_layout)
        main_layout.addLayout(hw_accel_layout)
        main_layout.addLayout(hint_layout)
        main_layout.addSpacing(10)
        main_layout.addLayout(button_layout)
        main_layout.addSpacing(10)
        main_layout.addLayout(progress_layout)
        main_layout.addLayout(log_layout)
        
        main_widget.setLayout(main_layout)
        self.setCentralWidget(main_widget)
    
    def select_ffmpeg(self):
        file_path, _ = QFileDialog.getOpenFileName(self, "选择FFmpeg可执行文件", "", "可执行文件 (*.exe)")
        if file_path and os.path.exists(file_path):
            self.ffmpeg_path = file_path
            self.ffmpeg_path_edit.setText(file_path)
            # 自动扫描硬件加速选项
            self.update_hw_acceleration()
        else:
            QMessageBox.warning(self, "警告", "无效的 FFmpeg 文件路径")

    def select_file(self):
        file_path, _ = QFileDialog.getOpenFileName(self, "选择视频文件", "", "视频文件 (*.mp4 *.avi *.mkv *.mov *.wmv)")
        if file_path:
            self.input_files = [file_path]
            self.input_path_edit.setText(file_path)

    def select_folder(self):
        folder_path = QFileDialog.getExistingDirectory(self, "选择文件夹")
        if folder_path:
            video_extensions = [".mp4", ".avi", ".mkv", ".mov", ".wmv"]
            self.input_files = [
                os.path.join(folder_path, file)
                for file in os.listdir(folder_path)
                if os.path.isfile(os.path.join(folder_path, file)) and
                   any(file.lower().endswith(ext) for ext in video_extensions)
            ]
            if self.input_files:
                self.input_path_edit.setText(f"{folder_path} (找到 {len(self.input_files)} 个视频文件)")
            else:
                self.input_path_edit.setText(f"{folder_path} (未找到视频文件)")
                QMessageBox.warning(self, "警告", "所选文件夹中没有找到视频文件")

    def toggle_black_line_width(self, state):
        self.black_line_width_edit.setEnabled(state == Qt.Checked)
    
    def preview_watermark(self):
        try:
            watermark_data = get_mark_data()
            image_data = base64.b64decode(watermark_data)
            pixmap = QPixmap()
            pixmap.loadFromData(image_data)
            preview_dialog = QMessageBox(self)
            preview_dialog.setWindowTitle("水印图片预览")
            preview_dialog.setText("这是将要添加到视频底部的图片:")
            preview_dialog.setIconPixmap(pixmap)
            preview_dialog.exec_()
        except Exception as e:
            QMessageBox.warning(self, "预览失败", f"无法预览水印图片: {str(e)}")

    
    # def preview_watermark(self):
    #     try:
    #         watermark_data = get_mark_data()
    #         fd, watermark_path = tempfile.mkstemp(suffix='.png')
    #         os.close(fd)
    #         with open(watermark_path, 'wb') as f:
    #             f.write(base64.b64decode(watermark_data))
            
    #         # 使用系统默认程序打开图片
    #         if platform.system() == "Windows":
    #             os.startfile(watermark_path)
    #         elif platform.system() == "Darwin":  # macOS
    #             subprocess.run(["open", watermark_path])
    #         else:  # Linux
    #             subprocess.run(["xdg-open", watermark_path])
                
    #         # 设置定时器在5秒后删除临时文件
    #         def cleanup_temp_file():
    #             try:
    #                 if os.path.exists(watermark_path):
    #                     os.remove(watermark_path)
    #             except Exception as e:
    #                 print(f"无法删除临时文件: {str(e)}")
            
    #         QTimer.singleShot(5000, cleanup_temp_file)
            
    #     except Exception as e:
    #         QMessageBox.warning(self, "错误", f"无法预览水印图片: {str(e)}")
    
    def update_hw_acceleration(self):
        """扫描可用的硬件加速选项"""
        if not self.ffmpeg_path or not os.path.exists(self.ffmpeg_path):
            QMessageBox.warning(self, "警告", "请先选择有效的 FFmpeg 可执行文件")
            return
        
        # 清除现有选项
        self.hw_accel_combo.clear()
        self.hw_accel_combo.addItem(HW_ACCEL_NONE)  # 始终添加CPU选项
        
        # 检测NVIDIA GPU
        try:
            nvidia_check = subprocess.run(
                [self.ffmpeg_path, "-hide_banner", "-encoders"],
                capture_output=True, text=True, check=True
            )
            if "h264_nvenc" in nvidia_check.stdout:
                self.hw_accel_combo.addItem(HW_ACCEL_NVIDIA)
        except Exception as e:
            print(f"检测NVIDIA GPU时出错: {str(e)}")
        
        # 检测AMD GPU
        try:
            amd_check = subprocess.run(
                [self.ffmpeg_path, "-hide_banner", "-encoders"],
                capture_output=True, text=True, check=True
            )
            if "h264_amf" in amd_check.stdout:
                self.hw_accel_combo.addItem(HW_ACCEL_AMD)
        except Exception as e:
            print(f"检测AMD GPU时出错: {str(e)}")
        
        # 检测Intel Quick Sync
        try:
            qsv_check = subprocess.run(
                [self.ffmpeg_path, "-hide_banner", "-encoders"],
                capture_output=True, text=True, check=True
            )
            if "h264_qsv" in qsv_check.stdout:
                self.hw_accel_combo.addItem(HW_ACCEL_INTEL)
        except Exception as e:
            print(f"检测Intel Quick Sync时出错: {str(e)}")
        
        # 如果只有CPU选项，显示提示
        if self.hw_accel_combo.count() == 1:
            QMessageBox.information(self, "硬件加速", "未检测到支持的硬件加速选项，将使用CPU模式")
        else:
            QMessageBox.information(self, "硬件加速", f"检测到 {self.hw_accel_combo.count() - 1} 种硬件加速选项")
    
    def start_processing(self):
        if not self.ffmpeg_path or not os.path.exists(self.ffmpeg_path):
            QMessageBox.warning(self, "警告", "请先选择有效的 FFmpeg 可执行文件")
            return

        if not self.input_files:
            QMessageBox.warning(self, "警告", "请选择输入文件或文件夹")
            return

        try:
            time_offset = int(self.offset_edit.text().strip() or 0)
            if time_offset <= 0:
                raise ValueError("时间偏移必须大于0")
                
            black_line_width = 1
            if self.black_line_checkbox.isChecked():
                black_line_width = int(self.black_line_width_edit.text().strip() or 1)
                if black_line_width <= 0:
                    raise ValueError("黑线宽度必须大于0")
            
            # 获取水印尺寸
            watermark_size = 1.0
            if self.watermark_checkbox.isChecked():
                try:
                    watermark_size = float(self.watermark_size_edit.text().strip() or 1.0)
                    if watermark_size <= 0:
                        raise ValueError("水印尺寸必须大于0")
                except ValueError:
                    raise ValueError("水印尺寸必须是有效的数字")
            
            # 获取硬件加速选项
            hw_accel = "cpu"
            if self.hw_accel_combo.currentText() == HW_ACCEL_NVIDIA:
                hw_accel = "nvidia"
            elif self.hw_accel_combo.currentText() == HW_ACCEL_AMD:
                hw_accel = "amd"
            elif self.hw_accel_combo.currentText() == HW_ACCEL_INTEL:
                hw_accel = "qsv"
            
            # 创建处理线程
            self.processing_thread = VideoProcessingThread(
                self.ffmpeg_path,
                self.input_files,
                time_offset,
                self.black_line_checkbox.isChecked(),
                black_line_width,
                self.watermark_checkbox.isChecked(),
                watermark_size,
                hw_accel
            )
            
            # 连接信号
            self.processing_thread.progress_update.connect(self.update_progress)
            self.processing_thread.processing_file.connect(self.update_current_file)
            self.processing_thread.finished_processing.connect(self.processing_finished)
            self.processing_thread.error_occurred.connect(self.processing_error)
            self.processing_thread.log_message.connect(self.update_log)  # 连接日志信号
            
            # 更新UI状态
            self.process_button.setEnabled(False)
            self.cancel_button.setEnabled(True)
            self.progress_bar.setValue(0)
            
            # 启动线程
            self.processing_thread.start()
            
        except ValueError as e:
            QMessageBox.warning(self, "输入错误", str(e))
        except Exception as e:
            QMessageBox.critical(self, "错误", f"启动处理时出错: {str(e)}")
    
    def cancel_processing(self):
        if self.processing_thread and self.processing_thread.isRunning():
            reply = QMessageBox.question(
                self, "确认取消", 
                "确定要取消当前处理吗？这将终止所有正在进行的操作。",
                QMessageBox.Yes | QMessageBox.No, 
                QMessageBox.No
            )
            
            if reply == QMessageBox.Yes:
                self.update_current_file("正在取消处理...")
                self.processing_thread.stop()
                self.processing_thread.wait()  # 等待线程结束
                self.processing_finished()
    
    def update_progress(self, current, total):
        percentage = int((current / total) * 100) if total > 0 else 0
        self.progress_bar.setValue(percentage)
    
    def update_current_file(self, message):
        self.current_file_label.setText(message)
    
    def processing_finished(self):
        self.process_button.setEnabled(True)
        self.cancel_button.setEnabled(False)
        self.current_file_label.setText("处理完成")
        self.progress_bar.setValue(100)
    
    def processing_error(self, error_message):
        QMessageBox.critical(self, "处理错误", error_message)
    
    def show_gpu_info(self):
        """显示GPU和FFmpeg兼容性信息"""
        if not self.ffmpeg_path or not os.path.exists(self.ffmpeg_path):
            QMessageBox.warning(self, "警告", "请先选择有效的 FFmpeg 可执行文件")
            return
            
        try:
            # 获取FFmpeg版本信息
            ffmpeg_version = subprocess.run(
                [self.ffmpeg_path, "-version"],
                capture_output=True, text=True, check=True
            )
            
            # 获取NVIDIA编码器信息
            nvidia_info = subprocess.run(
                [self.ffmpeg_path, "-hide_banner", "-h", "encoder=h264_nvenc"],
                capture_output=True, text=True
            )
            
            # 获取NVIDIA GPU列表信息
            nvidia_gpu_list = subprocess.run(
                [self.ffmpeg_path, "-hide_banner", "-h", "encoder=h264_nvenc", "-gpu", "list"],
                capture_output=True, text=True
            )
            
            # 获取CUDA信息
            cuda_info = subprocess.run(
                [self.ffmpeg_path, "-hide_banner", "-hwaccels"],
                capture_output=True, text=True
            )
            
            # 获取AMD编码器信息
            amd_info = subprocess.run(
                [self.ffmpeg_path, "-hide_banner", "-h", "encoder=h264_amf"],
                capture_output=True, text=True
            )
            
            # 获取Intel编码器信息
            intel_info = subprocess.run(
                [self.ffmpeg_path, "-hide_banner", "-h", "encoder=h264_qsv"],
                capture_output=True, text=True
            )
            
            # 创建详细信息对话框
            info_dialog = QDialog(self)
            info_dialog.setWindowTitle("GPU和FFmpeg兼容性信息")
            info_dialog.setMinimumSize(700, 500)
            
            layout = QVBoxLayout()
            
            # 创建选项卡小部件
            tabs = QTabWidget()
            
            # FFmpeg版本选项卡
            ffmpeg_tab = QWidget()
            ffmpeg_layout = QVBoxLayout()
            ffmpeg_text = QTextEdit()
            ffmpeg_text.setReadOnly(True)
            ffmpeg_text.setText(ffmpeg_version.stdout)
            ffmpeg_layout.addWidget(ffmpeg_text)
            ffmpeg_tab.setLayout(ffmpeg_layout)
            
            # NVIDIA选项卡
            nvidia_tab = QWidget()
            nvidia_layout = QVBoxLayout()
            nvidia_text = QTextEdit()
            nvidia_text.setReadOnly(True)
            
            # 添加NVIDIA GPU列表信息和CUDA信息
            if nvidia_info.returncode == 0:
                nvidia_content = f"NVIDIA编码器信息:\n\n{nvidia_info.stdout}\n\n"
                nvidia_content += f"NVIDIA GPU列表:\n\n{nvidia_gpu_list.stdout if nvidia_gpu_list.returncode == 0 else '无法获取GPU列表'}\n\n"
                nvidia_content += f"CUDA硬件加速信息:\n\n{cuda_info.stdout if cuda_info.returncode == 0 else '无法获取CUDA信息'}\n\n"
                nvidia_content += "常见错误代码:\n4294967256 - 通常表示CUDA初始化失败或GPU不兼容\n"
                nvidia_text.setText(nvidia_content)
            else:
                nvidia_text.setText("未检测到NVIDIA编码器或不支持")
                
            nvidia_layout.addWidget(nvidia_text)
            nvidia_tab.setLayout(nvidia_layout)
            
            # AMD选项卡
            amd_tab = QWidget()
            amd_layout = QVBoxLayout()
            amd_text = QTextEdit()
            amd_text.setReadOnly(True)
            amd_text.setText(amd_info.stdout if amd_info.returncode == 0 else "未检测到AMD编码器或不支持")
            amd_layout.addWidget(amd_text)
            amd_tab.setLayout(amd_layout)
            
            # Intel选项卡
            intel_tab = QWidget()
            intel_layout = QVBoxLayout()
            intel_text = QTextEdit()
            intel_text.setReadOnly(True)
            intel_text.setText(intel_info.stdout if intel_info.returncode == 0 else "未检测到Intel编码器或不支持")
            intel_layout.addWidget(intel_text)
            intel_tab.setLayout(intel_layout)
            
            # 添加选项卡
            tabs.addTab(ffmpeg_tab, "FFmpeg版本")
            tabs.addTab(nvidia_tab, "NVIDIA")
            tabs.addTab(amd_tab, "AMD")
            tabs.addTab(intel_tab, "Intel")
            
            layout.addWidget(tabs)
            
            # 添加关闭按钮
            close_button = QPushButton("关闭")
            close_button.clicked.connect(info_dialog.accept)
            layout.addWidget(close_button)
            
            info_dialog.setLayout(layout)
            info_dialog.exec_()
            
        except Exception as e:
            QMessageBox.critical(self, "错误", f"获取GPU信息时出错: {str(e)}")
    
    def closeEvent(self, event):
        if self.processing_thread and self.processing_thread.isRunning():
            reply = QMessageBox.question(
                self, "确认退出", 
                "处理仍在进行中。确定要退出吗？这将终止所有正在进行的操作。",
                QMessageBox.Yes | QMessageBox.No, 
                QMessageBox.No
            )
            
            if reply == QMessageBox.Yes:
                self.processing_thread.stop()
                self.processing_thread.wait()  # 等待线程结束
                event.accept()
            else:
                event.ignore()
        else:
            event.accept()
    
    def update_log(self, message):
        """更新日志显示框"""
        self.log_text.append(message)
        # 自动滚动到底部
        scrollbar = self.log_text.verticalScrollBar()
        scrollbar.setValue(scrollbar.maximum())


if __name__ == "__main__":
    app = QApplication(sys.argv)
    window = MainWindow()
    window.show()
    sys.exit(app.exec_())